home *** CD-ROM | disk | FTP | other *** search
/ Aminet 8 / Aminet 8 (1995)(GTI - Schatztruhe)[!][Oct 1995].iso / Aminet / mus / play / tracker_4_31.lzh / tracker / Amiga / wb2cli.c < prev    next >
C/C++ Source or Header  |  1995-01-13  |  3KB  |  110 lines

  1. /* wb2cli.c */
  2.  
  3. #include <exec/exec.h>
  4. #include <exec/ports.h>
  5. #include <exec/memory.h>
  6. #include <dos/dos.h>
  7. #include <dos/dosextens.h>
  8. #include <workbench/startup.h>
  9. #include <proto/exec.h>
  10. #include <proto/dos.h>
  11.  
  12. /* Undocumented DOS structure */
  13.  
  14. struct PathEntry
  15.    {
  16.    BPTR pe_Next;
  17.    BPTR pe_Lock;
  18.    };
  19.  
  20. /* to use local DOSBase */
  21. #define DOSBase dosbase
  22.  
  23.  
  24. /* WB2CLI, inspired by Mike Sinz idea */
  25.  
  26. LONG __asm WB2CLI(
  27.    register __a0 struct WBStartup *wbmsg, 
  28.    register __d0 ULONG defaultstack, 
  29.    register __a1 struct DosLibrary *dosbase)
  30.    {
  31.    struct Process *this_task, *wbtask;
  32.    struct CommandLineInterface *this_cli, *wbcli;
  33.    struct MsgPort *wbport;
  34.    LONG *this_path_pointer;
  35.    struct PathEntry *wbentry, *new_entry;
  36.    
  37.       /* get the current task */
  38.    this_task = (struct Process *)FindTask(0);
  39.  
  40. /* was:  this_task = (struct Process *)AbsExecBase->ThisTask; */
  41.  
  42.       /* if there is already a CLI, or we don't have a WBStartup, exit gracefully */
  43.    this_cli = BADDR(this_task->pr_CLI);
  44.    if (this_cli || !wbmsg)
  45.       goto end;
  46.  
  47.       /*** 
  48.        *** Add a new cli structure
  49.        ***/
  50.  
  51.    this_cli = (struct CommandLineInterface *)AllocDosObject(DOS_CLI, NULL);
  52.    if (!this_cli)
  53.       goto end;
  54.       /* link it into the current task (free it at end) */
  55.    this_task->pr_CLI = MKBADDR(this_cli);
  56.    this_task->pr_Flags |= PRF_FREECLI;
  57.       /* set up default stack */
  58.    this_cli->cli_DefaultStack = (defaultstack + 3) >>2;
  59.  
  60.  
  61.    Forbid();
  62.    
  63.       /***
  64.        ***     Find the workbench process
  65.        ***/
  66.       
  67.       /* we check all the cases that could go bad */
  68.    wbport = wbmsg->sm_Message.mn_ReplyPort;
  69.    if (!wbport || wbport->mp_Flags & PF_ACTION)
  70.       goto permit;
  71.    wbtask = wbport->mp_SigTask;
  72.    if (wbtask->pr_Task.tc_Node.ln_Type != NT_PROCESS || !wbtask->pr_CLI)
  73.       goto permit;
  74.    wbcli = BADDR(wbtask->pr_CLI);
  75.       
  76.       /* clone prompt if any */
  77.    if (wbcli->cli_Prompt)
  78.       SetPrompt(BADDR(wbcli->cli_Prompt + 1));
  79.  
  80.       /***
  81.        ***     Clone the path
  82.        ***/
  83.        
  84.       /* this strange way to go, together with MEMF_CLEAR,
  85.        * ensures we don't have to take action in case anything goes bad
  86.        */
  87.    this_path_pointer = &(this_cli->cli_CommandDir);
  88.    for (wbentry = BADDR(wbcli->cli_CommandDir); wbentry; wbentry = BADDR(wbentry->pe_Next))
  89.       {
  90.          /* note we HAVE to use AllocVec, since the path won't be freed by us */
  91.       new_entry = AllocVec(sizeof(struct PathEntry), MEMF_CLEAR | MEMF_PUBLIC);
  92.       if (!wbentry)
  93.          goto permit;
  94.       new_entry->pe_Lock = DupLock(wbentry->pe_Lock);
  95.       if (!new_entry)
  96.          {
  97.          FreeVec(new_entry);
  98.          goto permit;
  99.          }
  100.       *this_path_pointer = MKBADDR(new_entry);
  101.       this_path_pointer = &(new_entry->pe_Next);
  102.       }
  103.       
  104. permit:
  105.    Permit();
  106.  
  107. end:
  108.    return (LONG)this_cli;
  109.    }
  110.